package com.skh.array;

import java.util.Arrays;

/**
 * @Author skh
 * @Date 2020/3/14 09:51
 * @Desc 最长子序列
 */
public class LengthOfLIS {
    /**
     * 给定一个无序的整数数组，找到其中最长上升子序列的长度。
     *
     * 示例:
     *
     * 输入: [10,9,2,5,3,7,101,18]
     * 输出: 4
     * 解释: 最长的上升子序列是 [2,3,7,101]，它的长度是 4。
     * 说明:
     *
     * 可能会有多种最长上升子序列的组合，你只需要输出对应的长度即可。
     * 你算法的时间复杂度应该为 O(n2) 。
     * 进阶: 你能将算法的时间复杂度降低到 O(n log n) 吗?
     *
     */

    //动态规划
    public int lengthOfLIS(int[] nums) {
        if (nums.length == 0) {
            return 0;
        }

        int result = 0;
        int[] dp = new int[nums.length]; //dp[i]的值代表nums前i个数字的最长子序列长度
        //初始化为1,表示每个单个数都是上升子序列
        Arrays.fill(dp, 1);
        for (int i = 0; i < nums.length; i++) {
            for (int j = 0; j < i; j++) {
                if (nums[j] < nums[i]) {
                    dp[i] = Math.max(dp[i], dp[j] + 1);
                }
            }

            result = Math.max(result, dp[i]); //返回dp列表的最大值,即可得到全局最长上升子序列.
        }

        return result;
    }

    public static void main(String[] args) {
        LengthOfLIS lengthOfLIS = new LengthOfLIS();
        int[] nums = {10,9,2,5,3,7,21,18};
        int i = lengthOfLIS.lengthOfLIS(nums);
        System.out.println("i = " + i);
    }
}
